package cn.kawa.basic.service.impl;

import cn.kawa.basic.dto.SmsDto;
import cn.kawa.basic.exception.BusinessException;
import cn.kawa.basic.service.IVerifyCodeService;
import cn.kawa.basic.util.StrUtils;
import cn.kawa.basic.util.VerifyCodeUtils;
import cn.kawa.user.domain.User;
import cn.kawa.user.mapper.UserMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import java.util.concurrent.TimeUnit;

@Service
public class VerifyCodeServiceImpl implements IVerifyCodeService {

    @Autowired
    private RedisTemplate redisTemplate;

    @Autowired
    private UserMapper userMapper;

    /**
     * 手机验证码注册流程：
     *
     * @param key
     * @return
     */
    @Override
    public String getVerifyCode(String key) {
        //1.校验页面传值是否为空
        if(StringUtils.isEmpty(key)){
            throw new BusinessException("参数异常");
        }

        //2.生成随机验证码
        String code = StrUtils.getComplexRandomString(4);
        //System.out.println(code);
        //3.存入redis中，设置过期时间  3
        redisTemplate.opsForValue().set(key,code,3, TimeUnit.MINUTES);

        return VerifyCodeUtils.verifyCode(80,40,code);
    }

    @Override
    public void sendSmsCode(SmsDto smsDto) {
        //System.out.println(smsDto);
        String phone = smsDto.getPhone();
        String inputImgCode = smsDto.getImageCode();
        String imageCodeKey = smsDto.getImageCodeKey();


        //1.校验 - 空值校验  : 为空的话 isEmpty为true
        if(StringUtils.isEmpty(phone)){
            throw new BusinessException("手机号码不能为空!");
        }
        if(StringUtils.isEmpty(inputImgCode)){
            throw new BusinessException("图片验证嘛不能为空!");
        }
        if(StringUtils.isEmpty(imageCodeKey)){
            throw new BusinessException("请重新获取图片验证码!");
        }

        //2.校验 - 图形验证码校验 - 是否过期
        Object redisImgCode = redisTemplate.opsForValue().get(imageCodeKey);
        if(redisImgCode==null){
            throw new BusinessException("图形验证码过期!");
        }

        //3.校验 - 图形验证码校验 - 是否正确
        if(!inputImgCode.equalsIgnoreCase(redisImgCode.toString())){
            throw new BusinessException("图形验证码错误!");
        }

        //4.校验 - 手机号码是否注册过
        //w为什么用User：因为此模块是user表的操作，如果用logininfo会和emp信息混淆
        User user=userMapper.loadByPhone(phone);
        if(user!=null){
            throw new BusinessException("账号已注册!");
        }

        //5.获取手机验证码 - 判断是否过期
        Object redisSmsCode = redisTemplate.opsForValue().get("register:" + phone);
        String code =null;
        if(redisSmsCode==null){//第一次发送，或者已过期
            code = StrUtils.getComplexRandomString(6);
        }else{//验证码没有过期,就使用以前的验证码
            //6.没有过期，判断是否过了重发时间
            long redisTime = Long.parseLong(redisSmsCode.toString().split(":")[1]);
            if((System.currentTimeMillis()-redisTime)<1*60*1000){
                throw new BusinessException("请勿重复获取!");
            }else {
                code = redisSmsCode.toString().split(":")[0];
            }

        }
        /**
         * 此处是不管是验证码没过期，还是第一次获取验证码的后续操作;
         * 若是第一，就存入redis
         */
        //7.将验证码存入redis:  [register:131564646 - 4399:12346464611]
        redisTemplate.opsForValue().set("register:"+phone,code+":"+System.currentTimeMillis(),3, TimeUnit.MINUTES);
        //8.调用SmsUtils发送短信
        //SmsUtil.sendSms(phone,"手机验证码为"+code+"请在3分钟内使用");
        System.out.println("手机验证码为"+code+"请在3分钟内使用");

    }

    /**
     * 用于微信登录绑定user 时的发送短信验证码功能
     * @param smsDto
     */
    @Override
    public void binderSmsCode(SmsDto smsDto) {
        //System.out.println(smsDto);
        String phone = smsDto.getPhone();

        //1.校验 - 空值校验  : 为空的话 isEmpty为true
        if(StringUtils.isEmpty(phone)){
            throw new BusinessException("手机号码不能为空!");
        }

        //2.获取手机验证码 - 判断是否过期   业务键 binder:111222444 值 4396：时间戳
        Object redisSmsCode = redisTemplate.opsForValue().get("binder:" + phone);
        String code =null;
        if(redisSmsCode==null){//第一次发送，或者已过期
            code = StrUtils.getComplexRandomString(6);
        }else{//验证码没有过期,就使用以前的验证码
            //6.没有过期，判断是否过了重发时间
            long redisTime = Long.parseLong(redisSmsCode.toString().split(":")[1]);
            if((System.currentTimeMillis()-redisTime)<1*60*1000){
                throw new BusinessException("请勿重复获取!");
            }else {
                code = redisSmsCode.toString().split(":")[0];
            }

        }
        /**
         * 此处是不管是验证码没过期，还是第一次获取验证码的后续操作;
         * 若是第一，就存入redis
         */
        //3.将验证码存入redis:  [register:131564646 - 4399:12346464611]
        redisTemplate.opsForValue().set("binder:"+phone,code+":"+System.currentTimeMillis(),3, TimeUnit.MINUTES);
        //4.调用SmsUtils发送短信
        //SmsUtil.sendSms(phone,"手机验证码为"+code+"请在3分钟内使用");
        System.out.println(phone+"：您的手机验证码为"+code+"请在3分钟内使用");
    }


}
